﻿function K_NS()
{
	//base data object
	function K_TreeData()
	{
	}
	//register a tree item to data
	K_TreeData.prototype.registerItem=function(item)
	{
		item.data=this;
	}
	//return the root tree item
	K_TreeData.prototype.getRootItem=function()
	{
		if(!this.rootItem)
		{
			var i=this.rootItem=this.readRootItem();
			if(i)
			{
				this.registerItem(i);
			}
		}
		return this.rootItem;
	}
	//return the first child item of a menu item
	K_TreeData.prototype.getItemFirstChild=function(item)
	{
		if(!item.firstChild)
		{
			var i=item.firstChild=this.readItemFirstChild(item);
			if(i)
			{
				i.parentItem=item;
				this.registerItem(i);
			}
		}
		return item.firstChild;
	}
	//return the next sibling child item of a menu item
	K_TreeData.prototype.getItemNextSibling=function(item)
	{
		if(!item.parentItem){return null;}
		if(!item.nextSibling)
		{
			var i=item.nextSibling=this.readItemNextSibling(item);
			if(i)
			{
				i.previousSibling=item;
				i.parentItem=item.parentItem;
				this.registerItem(item.nextSibling);
			}
		}
		return item.nextSibling;
	}
	//return a item from item's id
	K_TreeData.prototype.getItemByid=function(id)
	{
		var item=this.itemids[id];
		if(item){return item;}
		if(!this.lastItem){this.lastItem=this.getRootItem();}
		while(this.lastItem=this.lastItem.getNextItem())
		{
			if(this.lastItem.getProperty("id")==id)
			{
				return this.lastItem;
			}
		}
		return null;
	}
	//upgrade a item to parent level
	K_TreeData.prototype.upgradeItem=function(item)
	{
		var parent=item.getParentItem();
		if(!parent || parent==this.rootItem){return false;}
		var cItem=item.getFirstChild(),nItem=item.getNextSibling(),pItem=item.getPreviousSibling();
		if(parent.getFirstChild()==item)
		{
			parent.firstChild=null;
			parent.setProperty("hasChild",false);
			parent.update();
		}
		if(nItem)
		{
			for(var child=nItem;child;child=child.getNextSibling())
			{
				child.parentItem=item;
			}
			nItem.previousSibling=item.getLastChild();
			if(nItem.previousSibling){nItem.previousSibling.nextSibling=nItem;}
			if(!cItem)
			{
				item.firstChild=nItem;
			}
			item.setProperty("hasChild",true);
			item.update();
		}
		if(pItem){pItem.nextSibling=null;}
		item.previousSibling=parent;
		if(parent.getNextSibling())
		{
			parent.getNextSibling().previousSibling=item;
		}
		item.nextSibling=parent.getNextSibling();
		parent.nextSibling=item;
		item.parentItem=parent.getParentItem();
		return true;
	}
	//degrade a item to children level
	K_TreeData.prototype.degradeItem=function(item)
	{
		var pItem=item.getPreviousSibling();
		if(!pItem){return false;}
		var parent=item.getParentItem(),nItem=item.getNextSibling(),cItem=item.getFirstChild();

		item.parentItem=pItem;
		item.previousSibling=pItem.getLastChild();
		if(item.previousSibling)
		{
			item.previousSibling.nextSibling=item;
		}
		else
		{
			pItem.firstChild=item;
			pItem.setProperty("hasChild",true);
			pItem.update();
		}

		if(nItem){nItem.previousSibling=pItem;}
		pItem.nextSibling=nItem;
		item.nextSibling=null;
		return true;
	}
	K_TreeData.prototype.addItem=function(parent,pItem)
	{
		var returnObj={returnValue:true};
		SFEvent.trigger(this,"beforeitemadd",[returnObj,parent,pItem]);
		if(!returnObj.returnValue)
		{
			return null;
		}

		var newItem=this.createItem(parent,pItem);
		this.registerItem(newItem);
		newItem.parentItem=parent;
		if(!parent.getFirstChild())
		{
			parent.setProperty("hasChild",true);
		}
		if(!pItem)
		{
			newItem.previousSibling=null;
			newItem.nextSibling=parent.getFirstChild();
			if(newItem.nextSibling)
			{
				newItem.nextSibling.previousSibling=newItem;
			}
			newItem.nextSibling=parent.getFirstChild();
			parent.firstChild=newItem;
		}
		else
		{
			newItem.previousSibling=pItem;
			newItem.nextSibling=pItem.getNextSibling();
			if(newItem.nextSibling)
			{
				newItem.nextSibling.previousSibling=newItem;
			}
			pItem.nextSibling=newItem;
		}
		SFEvent.trigger(this,"afteritemadd",[newItem]);
		return newItem;
	}
	K_TreeData.prototype.deleteItem=function(item)
	{
		var returnObj={returnValue:true};
		SFEvent.trigger(this,"beforeitemdelete",[returnObj,item]);
		if(!returnObj.returnValue){return false;}
		var parent=item.getParentItem();
		this.removeItem(item,0);
		if(parent.getFirstChild()==item)
		{
			parent.firstChild=item.getNextSibling();
		}
		if(parent && parent.hasChild)
		{
			if(!parent.getFirstChild())
			{
				parent.setProperty("hasChild",false);
				parent.update();
			}
		}
		item.previousSibling=null;
		item.nextSibling=null;
		return true;
	}
	K_TreeData.prototype.removeItem=function(item,level)
	{
		if(item.getFirstChild())
		{
			for(var child=item.getLastChild();child;)
			{
				this.removeItem(child,level+1);
				var c=child.getPreviousSibling();
				child.previousSibling=null;
				child.parentItem=null;
				child=c;
			}
			item.firstChild=null;
		}
		if(level>0)
		{
			var pt=item.getPreviousSibling()
			if(pt){pt.nextSibling=null;}
		}
		else
		{
			var pt=item.getPreviousSibling(),nt=item.getNextSibling();
			if(pt){pt.nextSibling=nt;}
			if(nt){nt.previousSibling=pt;}
		}
		this.clearItem(item);
		SFEvent.trigger(this,"afteritemdelete",[item,level]);
	}
	K_TreeData.prototype.moveItem=function(item,flagItem,dir)
	{
		if(item.getProperty("OutlineLevel")<flagItem.getProperty("OutlineLevel") && item==flagItem.getAncestorItem(item.getProperty("OutlineLevel")))
		{
			return false;
		}
		var returnObj={returnValue:true};
		SFEvent.trigger(this,"beforeitemmove",[returnObj,item,flagItem,dir]);
		if(!returnObj.returnValue){return false;}
		var parentItem=item.getParentItem(),previousSibling=item.getPreviousSibling(),nextSibling=item.getNextSibling();
		if(parentItem.getFirstChild()==item)
		{
			parentItem.firstChild=nextSibling;
		}
		item.parentItem=null;
		if(previousSibling)
		{
			previousSibling.nextSibling=nextSibling;
			item.previousSibling=null;
		}
		if(nextSibling)
		{
			nextSibling.previousSibling=previousSibling;
			item.nextSibling=null;
		}
		var pItem,preItem=null,postItem=null;
		if(dir)
		{
			var nItem=flagItem.getNextViewItem();
			if(!nItem || nItem.getProperty("OutlineLevel")<flagItem.getProperty("OutlineLevel"))
			{
				preItem=flagItem;
			}
			else
			{
				postItem=nItem;
			}
		}
		else
		{
			var pItem=flagItem.getPreviousViewItem();
			if(!pItem || pItem.getProperty("OutlineLevel")<=flagItem.getProperty("OutlineLevel"))
			{
				postItem=flagItem;
			}
			else
			{
				preItem=pItem;
			}
		}
		if(preItem)
		{
			item.parentItem=preItem.getParentItem();
			item.previousSibling=preItem;
			item.nextSibling=preItem.getNextSibling();
			preItem.nextSibling=item;
			if(item.nextSibling)
			{
				item.nextSibling.previousSibling=item;
			}
		}
		else
		{
			item.parentItem=postItem.getParentItem();
			item.nextSibling=postItem;
			item.previousSibling=postItem.getPreviousSibling();
			if(!item.previousSibling)
			{
				item.parentItem.firstChild=item;
			}
			postItem.previousSibling=item;
			if(item.previousSibling)
			{
				item.previousSibling.nextSibling=item;
			}
		}
		parentItem.updateOutline(true);
		item.parentItem.updateOutline(true);
		SFEvent.trigger(this,"afteritemmove",[item,level]);
	}

	//read a root item
	K_TreeData.prototype.readRootItem=function()
	{
		return null;
	}

	//read first child item of a item
	K_TreeData.prototype.readItemFirstChild=function(item)
	{
		return null;
	}

	//read the next sibling item of a item
	K_TreeData.prototype.readItemNextSibling=function(item)
	{
		return null;
	}
	//run when item update
	K_TreeData.prototype.updateItem=function(item,property,value)
	{
	}
	//create a new item
	K_TreeData.prototype.createItem=function(parent,pItem)
	{
		return new K_TreeItem();
	}
	//clear item
	K_TreeData.prototype.clearItem=function(item)
	{
	}
	window.K_TreeData=K_TreeData;
}
K_NS();